
#include <memory.h>
#include <stdio.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include <time.h>


#include "radio.h"
#include "radio_config.h"

/*
PI0  :	Program is running, led 
PI1  :	Tx status,  led
PI2  :	Rx status,  led
PI3  :	prepare to tx, switch on,  after finish tx, switch off 

PI4 :
PI5 :
PI6 :

PI7  :	button : start capture picture and send data.          input

PI8 :
--
PI15 :

or PI4-PI9(SD3)
*/
#define PI_CFG0_REG         		(0xf1c20800+0x120)
#define PI_DAT_REG         			(0xf1c20800+0x130)

#define PI_PROGAM_RUN(bset)  		PI0_6_WRITE_BIT(0, bset)
#define PI_PROGAM_TX(bset)  		PI0_6_WRITE_BIT(1, bset)
#define PI_PROGAM_RX(bset)  		PI0_6_WRITE_BIT(2, bset)
#define PI_PROGAM_TXON(bset)  		PI0_6_WRITE_BIT(3, bset)

#define PI_PROGAM_TRIG_TX(bset)  		( memRead(PI_DAT_REG) & (1 << 7) )
	
#define PA_CFG0_REG           		0xf1c20800
#define PA_DAT_REG         	  	0xf1c20810		

#define PB_CFG1_REG        	  	0xf1c20828		
#define PG_CFG0_REG        		(0xf1c208D8)
#define PG_CFG1_REG        		(0xf1c208DC)
#define PG_DAT_REG         	 	0xf1c208E8		

extern tRadioConfiguration * pRadioConfiguration;

#define RET_NUM   2
#define FILE_LEN   12

int sendRepeat = 0;
#define  MAGIC_NUM  0XA3

#define MAX_JPG_SIZE           6 * 1024 * 1024
#define RADIO_PACKET_LENGTH    pRadioConfiguration->Radio_PacketLength    //RADIO_CONFIGURATION_DATA_RADIO_PACKET_LENGTH

int g_memFd = -1 ;
int *dmaBuff = NULL;
#define MAX_DMA_SIZE    1024
#define __REG(x)        (*((volatile unsigned int *)(x)))   
char devName[126];
int buf[4];
unsigned char JpgTransBuf[ MAX_JPG_SIZE ];  //max jpg size: 6M
char jpgFileFullPath[] = "/data/lhg/send.jpg";
int jpgLen = 0, curTransPos = 0;

int jpgRead( char * fileName, unsigned char * readBuf )
{
	int fp, size;
	int readCount = 0;
	printf("open :%s, line:%d\n", fileName, __LINE__);
	if((fp = open(fileName, O_RDONLY )) == -1 )
        {
            printf("open %s error\n", fileName );
			return -1;
        }
	printf(", line:%d\n", __LINE__);
	if( (size = lseek( fp , 0L, SEEK_END)) == -1)
		{
            printf("%s :FSEEK to end  error\n", fileName );
			close(fp);  
			return -1;
        }
	printf(", line:%d,size:%d\n", __LINE__ , size);
	if( lseek( fp , 0L, SEEK_SET) != 0)
		{
            printf("%s: FSEEK to begin error\n", fileName );
			close(fp);  
			return -1;
        } 
	readCount = read( fp, readBuf , size  );
	if( readCount < 0 )
		{
            printf("FILE read error \n" );
			close(fp);  
			return -1;
        }
	
    close(fp);  
	
	return readCount;
	
}

inline unsigned int memRead(unsigned int addr)  
{
	return read( g_memFd, &addr, 4);
}

inline void memWrite( unsigned int addr, int value)  
{
	buf[0] = addr;
	buf[1] = value;
	write( g_memFd, &buf, 8);
}

inline void SPI_WRITE_BIT( int valueBit, int bSet) 
{
	static unsigned int P_Data = 0;
	#ifdef  CORE_BOARD 
	{
		if( P_Data == 0)
			P_Data = memRead( PA_DAT_REG ) ;
		if( bSet )
			P_Data |= (1 << valueBit);
		else
			P_Data &= (~(1 << valueBit) );
		memWrite( PA_DAT_REG ,  P_Data  ) ;
		
	}
	#endif
	#ifdef  DEV_BOARD 
	{
		if( P_Data == 0)
			P_Data = memRead( PG_DAT_REG ) ;
		if( bSet )
			P_Data |= (1 << valueBit);
		else
			P_Data &= (~(1 << valueBit) );
		memWrite( PG_DAT_REG ,  P_Data ) ;
	}
	#endif

}

inline void PI0_6_WRITE_BIT( int valueBit, int bSet) 
{
	static unsigned int PI_Data = 0;

	{
		if( PI_Data == 0)
			PI_Data = memRead( PI_DAT_REG ) ;
		if( bSet )
			PI_Data |= (1 << valueBit);
		else
			PI_Data &= (~(1 << valueBit) );
		memWrite( PI_DAT_REG ,  PI_Data ) ;
	}

}


/*
          rx                                tx(develop board)
SDN   3   PA9(CKO2)                     	PG0(PCLK)

NSEL  4   PA5(SPI3_CS0)                 	PG2(HSYNC)

SCK   5   PA6(SPI3_CLK)                 	PG4(D0)

SDI   6   PA7(SPI3_MOSI)                 	PG6(D2)

SD0   8   PA8(SPI3_MISO)   input           	PG8(D4)

NIRQ  7   PB10             input           	PG10(D6)

*/


int  openMemDev()
{
	unsigned int value;
    if( g_memFd == -1)
    {
        if((g_memFd = open(devName, O_RDWR | O_SYNC)) == -1)
        {
            printf("open %s error\n", devName );
			return -1;
        }

	#ifdef CORE_BOARD  //#defined in radio.h
		// mainboard
		value = memRead( PA_CFG0_REG ) ;
		value = (value & 0x000fffff ) | 0x11100000;//pa5,6,7
		memWrite( PA_CFG0_REG , value ) ;
 		value = memRead( PA_CFG0_REG + 4) ;
		value = (value & 0xffffff00 ) | 0x00000010;//pa8:input , 9: output
		memWrite( PA_CFG0_REG + 4 , value ) ;

		value = memRead( PB_CFG1_REG ) ;
		value = (value & 0xFFFff0ff ) ; //pB10:IRQ
		memWrite( PB_CFG1_REG , value ) ; 
	#else
		// dev board
		value = memRead( PG_CFG0_REG ) ;
		value = (value & 0xF0F0F0F0 ) | 0x01010101;//PG0-,PG2, PG4, PG6  OUTPUT, PG8,PG10:INPUT
		memWrite( PG_CFG0_REG , value ) ;

		value = memRead( PG_CFG1_REG ) ;
		value = (value & 0xFFFFF0F0 ) ;// PG8,PG10:INPUT
		memWrite( PG_CFG1_REG , value ) ;  
	#endif
#ifdef GPIO_BOARD

	memWrite( PI_CFG0_REG , 0x01111111 ) ;  //PI0 -,PI6: OUTPUT,   PI7 : INPUT
#endif

    }
	return 0;
}

 static int sending = 1;
 
 unsigned int sendNum = 0;
 #define PACKET_SEND_INTERVAL  1000u
short lPktSending = 0 ;
extern  void delay_ms(unsigned int time);
void DemoApp_Pollhandler()
{
  
   char isTransmit ;
   static int startTime = 0 , endTime = 0, PacketHeadNum = 0;
   int copyLen = 0;
  // Check if the radio packet sent successfully
  gRadio_CheckTransmitted( &isTransmit);
  if ( isTransmit )
  {
    /* Clear Packet Sending flag */
	//printf("t ok\n");
    lPktSending = 0;
	delay_ms(10);
  }

  if ( lPktSending <= 0)
  {
  	if( jpgLen <= 0) 
	{
		jpgLen = jpgRead(jpgFileFullPath,  JpgTransBuf );
		curTransPos = 0;
		sendNum = 0;
		PacketHeadNum = 0;
		if( jpgLen <= 0)
		{
			printf("read file error\n");
			return;
		}
		
#ifdef GPIO_BOARD
		PI_PROGAM_TXON( 1 );
#endif
		startTime = clock();
  	}
	else if( curTransPos < jpgLen )
	{
		if( sendNum != 0 )
		{
			pRadioConfiguration->Radio_CustomPayload[0] = sendNum & 0xff;
			pRadioConfiguration->Radio_CustomPayload[1] = (sendNum >> 8) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[2] = MAGIC_NUM;
			
			if( jpgLen - curTransPos >=  (RADIO_PACKET_LENGTH - 3) )
			{
				copyLen  = RADIO_PACKET_LENGTH - 3;
			}
			else
			{
				endTime = clock();
				copyLen = jpgLen - curTransPos;
				printf("send over:jpgLen:%d,packet:%d, time:%d , bps:%f\n", jpgLen , sendNum , endTime - startTime, (jpgLen * 8.0 ) / (endTime - startTime) * 1000.0  );
			}
			if( sendNum % 128 == 0) {
				printf("n:%d, L:%d\n", sendNum , copyLen );
#ifdef GPIO_BOARD
				PI_PROGAM_TX( (sendNum % 200 ) < 64);
#endif
			}
			memcpy( &pRadioConfiguration->Radio_CustomPayload[3] , &JpgTransBuf[curTransPos] , copyLen );
			++sendNum;
		}
		else //send packet header
		{
			printf("start send file head\n");
			pRadioConfiguration->Radio_CustomPayload[0] = sendNum & 0xff;
			pRadioConfiguration->Radio_CustomPayload[1] = (sendNum >> 8) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[2] = MAGIC_NUM;
			
			pRadioConfiguration->Radio_CustomPayload[3] = jpgLen & 0xff;
			pRadioConfiguration->Radio_CustomPayload[4] = (jpgLen >> 8) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[5] = (jpgLen >> 16) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[6] = (jpgLen >> 24) & 0xff;

			pRadioConfiguration->Radio_CustomPayload[7] = jpgLen & 0xff;
			pRadioConfiguration->Radio_CustomPayload[8] = (jpgLen >> 8) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[9] = (jpgLen >> 16) & 0xff;
			pRadioConfiguration->Radio_CustomPayload[10] = (jpgLen >> 24) & 0xff;
			
			memcpy( &pRadioConfiguration->Radio_CustomPayload[11] , jpgFileFullPath , FILE_LEN );
			copyLen = 0;
			if( PacketHeadNum++ > 1)
				sendNum = 1;
			usleep(2000000);
			printf("start send file\n");
		}
	    
		curTransPos += copyLen;
        vRadio_StartTx(pRadioConfiguration->Radio_ChannelNumber, (unsigned char *) &pRadioConfiguration->Radio_CustomPayload[0u]);
		lPktSending	 = 1u;
	}
	else  //send the last ending packet
	{
		pRadioConfiguration->Radio_CustomPayload[0] = 0xff;
		pRadioConfiguration->Radio_CustomPayload[1] = 0xff;
		vRadio_StartTx(pRadioConfiguration->Radio_ChannelNumber, (unsigned char *) &pRadioConfiguration->Radio_CustomPayload[0u]);
		sending ++;
	}
  }
}

	//input parameter:  magicNum , jpgFileFullPath
	int main(int argc,char *argv[])
	{

/*	if( argc < 2 )
	{
		printf("name,dev (like:memdis /dev/mem) \n");
		return 0;
	} */
	int  led = 0;
	strcpy(devName , "/dev/chrdev" );

	if( openMemDev() < 0)
		return 0;
	
   short i = 0;
   for(i = 0; i < 32; i++)
	pRadioConfiguration->Radio_CustomPayload[i] = i + 1;
   
   vRadio_Init();
   
	while( sendRepeat < RET_NUM )
	{
		sending = 0;
		lPktSending = 0;
		jpgLen = 0;
		++sendRepeat;
		while( sending < 3 )
		{
		
#ifdef GPIO_BOARD
		if( led % 128 == 0)
			PI_PROGAM_RUN( 1 );
		else if( led % 128 == 64)
			PI_PROGAM_RUN( 0 );
#endif
			DemoApp_Pollhandler();
		} 
		printf("send over\n");
		usleep(2000000);
		printf("start send\n");
	}
	
#ifdef GPIO_BOARD
		PI_PROGAM_TXON( 0 );
#endif
	
	}

    

